package com.gtmc.gclub.chat.service;

import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Queue;
import java.util.concurrent.ArrayBlockingQueue;

import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.collections.MapUtils;
import org.apache.commons.lang.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.gtmc.gclub.chat.config.ChatConfigParam;
import com.gtmc.gclub.chat.dto.ChatMessageDto;
import com.gtmc.gclub.chat.dto.ChatMsgDetailDto;
import com.gtmc.gclub.common.WxMaterialTypeEnum;

public class ChatWaitQueueService {
	private volatile boolean isFull = false;// 全局队列标志位
	private volatile List<String> usefulChats ;
	private static final Integer MAX_QUEUE_LENGTH = ChatConfigParam.CHAT_WAIT_QUEUE_MAX ;
	// 带有索引的真实消息等待队列
	private volatile Map<String,Queue<ChatMsgDetailDto>> waitQueues = new HashMap<String,Queue<ChatMsgDetailDto>>();
	// 以用户为索引的队列指针
	private volatile Map<String,String> userQueues = new HashMap<String,String>();
	// 以客服为索引的队列指针
	private volatile Map<String,String> chatQueues = new HashMap<String,String>();
	private static ChatWaitQueueService chatWaitQueueService;
	
	private static Logger logger = LoggerFactory.getLogger(ChatWaitQueueService.class);
	
	private ChatWaitQueueService() {};
	/**
	 * 全系统使用同一队列库
	 * @return
	 */
	public static ChatWaitQueueService newInstance() {
		if(chatWaitQueueService==null) {
			chatWaitQueueService = new ChatWaitQueueService();
		}
		return chatWaitQueueService;
	}
	/**
	 * 加入指定客服队列
	 * @param queueName 客服ID
	 * @param msgDetail 客户以及发送的内容
	 * @return	加入队列成功与否
	 */
	public boolean addQueue(String chatId,ChatMsgDetailDto msgDetail) {
		if(chatId==null) {
			return addQueue(msgDetail);
		}
		logger.debug("开始往"+chatId+"客服队列中增加客户消息"+msgDetail);
		// 找出客服队列
		Queue<ChatMsgDetailDto> queue = getChatQueue(chatId);
		// 判断队列还能否增加
		if(queue.size()>=MAX_QUEUE_LENGTH) {
			logger.debug("客服"+chatId+"等待队列以满");
			return false;
		}
		// 队列未满，修改全局标志
		if(isFull) {
			isFull = false;
		}
		return queue.offer(msgDetail);
	}
	/**
	 * 无指定客服，查找队列中最闲客服，加入等待队列
	 * @param msgDetail
	 * @return
	 */
	public boolean addQueue(ChatMsgDetailDto msgDetail) {
		logger.debug("开始往所有客服队列中增加客户消息"+msgDetail);
		logger.debug("查询此用户是否已经存在于等待队列中...");
		String userQueuePoint = userQueues.get(msgDetail.getFormeUser());
		logger.debug("用户在等待队列中的指针："+userQueuePoint);
		// 用户指针不为空，则说明用户一斤在队列中等待
		if(userQueuePoint!=null) {
			Queue<ChatMsgDetailDto> userQueueOnChatQueue = waitQueues.get(userQueuePoint);
			logger.debug("查询到用户已经存在于等待队列中，队列信息："+userQueueOnChatQueue);
			logger.debug("遍历查找到的客服队列，找到用户消息的位置，追加消息");
			for(ChatMsgDetailDto userMsgTempEntity : userQueueOnChatQueue) {
				if(StringUtils.equals(userMsgTempEntity.getFormeUser(), msgDetail.getFormeUser())) {
					if(msgDetail.getContent()==null) {
						logger.debug("新消息为null，则为消息重排重新进入的队列，非用户发送的消息，故只做队列操作，不做消息内容操作");
					}else {
						logger.debug("用户重复发送消息，原消息数组为："+userMsgTempEntity.getAllContent()+";新增消息为："+msgDetail.getContent());
						// 发送消息不为null则为用户重复发送消息
						// 修改消息数组，更新最后消息
						List<ChatMessageDto> oldContents = userMsgTempEntity.getAllContent();
						ChatMessageDto messageDto = new ChatMessageDto();
						messageDto.setContent(msgDetail.getContent());
						messageDto.setType(msgDetail.getMsgType());
						oldContents.add(messageDto);
						userMsgTempEntity.setAllContent(oldContents);
						userMsgTempEntity.setContent(msgDetail.getContent());
						logger.debug("消息数组追加后，最后消息更新之后，消息详细为："+userMsgTempEntity);
					}
					break;
				}
			}
			// 队列中既然已经存在此用户的消息了，那么更新消息内容就可以了，无需再修改队列结构
			return true;
		}
		if(!valiate()) {
			logger.debug("全局校验未通过，无法增加队列");
			return false;
		}
		int maxQueueLengthTemp = MAX_QUEUE_LENGTH;
		String targetChatId = "" ;
		logger.debug("遍历所有可用客服："+usefulChats);
		for(String chatId : usefulChats) {
			// 若客服队列指针为空，无等待队列，则直接插入到此队列中
			if(MapUtils.isEmpty(chatQueues)) {
				maxQueueLengthTemp=0;
				targetChatId = chatId;
				break;
			}
			String charQueueId = chatQueues.get(chatId);
			Queue<ChatMsgDetailDto> queue = waitQueues.get(charQueueId);
			logger.debug("客服"+chatId+"的等待队列长度:"+(queue==null ? "0" : queue.size())+"\n队列详细："+queue);
			// 若队列中无人，则就是它了
			if(CollectionUtils.isEmpty(queue)) {
				maxQueueLengthTemp=0;
				targetChatId = chatId;
				break;
			}
			if(queue.size()<maxQueueLengthTemp) {
				maxQueueLengthTemp = queue.size();
				targetChatId = chatId;
			}
		}
		logger.debug("遍历客服结束，最为空闲的客服："+targetChatId+"，其队列深度为："+maxQueueLengthTemp);
		if(maxQueueLengthTemp==MAX_QUEUE_LENGTH) {
			logger.debug("所有队列已满");
			isFull = true;
			return false;
		}
		// 队列未满，修改全局标志
		if(isFull) {
			isFull = false;
		}
		logger.debug("筛选出等待队列最少的客服:"+targetChatId);
		String charQueueId = chatQueues.get(targetChatId);
		// 若客服指针列表中不存在队列，则客服还未有任何队列信息在客服指针中，这时候，插入
		if(charQueueId==null) {
			// 为了避免指针级的重复，此处使用时间戳，key使用字符串
			String point = new Date().getTime()+"";
			logger.debug("客服"+targetChatId+"在队列中还未建立 ，现在建立新的队列，指针为"+point.toString());
			Queue<ChatMsgDetailDto> newQueue  = new ArrayBlockingQueue<ChatMsgDetailDto>(MAX_QUEUE_LENGTH);
			waitQueues.put(point.toString(), newQueue);
			chatQueues.put(targetChatId, point.toString());
			charQueueId = point.toString();
		}
		logger.debug("客服指针更新完毕，下面更新用户指针");
		if(MapUtils.isEmpty(userQueues)) {
			logger.debug("用户指针对象为空，新建");
			userQueues = new HashMap<String,String>();
		}
		if(userQueues.get(msgDetail.getFormeUser())==null) {
			logger.debug("用户指针不存在，插入指针");
			userQueues.put(msgDetail.getFormeUser(), charQueueId);
		}
		logger.debug("用户指针更新完毕："+userQueues.get(msgDetail.getFormeUser()));
		Queue<ChatMsgDetailDto> queue = waitQueues.get(charQueueId);
		logger.debug("取得客服"+targetChatId+"的队列"+queue);
		// 把设置的消息内容放入消息数组中
		if(msgDetail.getContent()==null) {
//			logger.debug("新消息为null，则为消息重排重新进入的队列，非用户发送的消息，故只做队列操作，不做消息内容操作");
			logger.debug("新消息不能为null，请检查");
		}else {
//			logger.debug("消息不为空，则为用户重复发送消息，此时需要更新消息内容，再入队列");
			List<ChatMessageDto> contentList = msgDetail.getAllContent();
			if(CollectionUtils.isEmpty(contentList)) {
				contentList = new ArrayList<ChatMessageDto>();
			}
			ChatMessageDto messageDto = new ChatMessageDto();
			messageDto.setContent(msgDetail.getContent());
			messageDto.setType(msgDetail.getMsgType());
			contentList.add(messageDto);
			msgDetail.setAllContent(contentList);
			logger.debug("设置消息结构，完善消息实体内容"+msgDetail);
		}
		// 添加一个元素并返回true       如果队列已满，则返回false
		return queue.offer(msgDetail);
	}
	/**
	 * 找出指定客服的等待队列
	 * @param chatId
	 * @return
	 */
	private Queue<ChatMsgDetailDto> getChatQueue(String chatId){
		// 找出客服队列指针
		String charQueueId = chatQueues.get(chatId);
		// 根据客服队列指针找出真实 客服队列
		return waitQueues.get(charQueueId);
	}
	/**
	 * 返回指定客服队列中的第一个元素
	 * 为什么设计为单取出队列中的消息元素：必须要客服和用户成功建立起聊天关系之后，才能删除等待队列中的等待消息
	 * @param chatId
	 * @return
	 */
	public ChatMsgDetailDto getChatQueueUser(String chatId) {
		Queue<ChatMsgDetailDto> userWaitQueue = getChatQueue(chatId);
		if(userWaitQueue==null || userWaitQueue.isEmpty()) {
			return null;
		}
		// 返回队列头部元素：先入先出
		return userWaitQueue.peek();
	}
	/**
	 * 返回指定客服队列中的第一个元素，并移除<br/>
	 * 不建议使用此方法，因为从客服等待队列中取出等待消息，并不一定就意味着客服就一定可以成功和用户建立聊天链接，<br/>
	 * 应当先调用getChatQueueUser(chatId)取出等待的消息，确保客服和用户已经建立链接，
	 * 然后再调用removeChatQueueUser(chatId,userId)移除等待队列中的等待消息<br/>
	 * @param chatId
	 * @return
	 */
	public ChatMsgDetailDto getChatQueueUserAndDeleteFromQueue(String chatId) {
		Queue<ChatMsgDetailDto> userWaitQueue = getChatQueue(chatId);
		if(userWaitQueue==null || userWaitQueue.isEmpty()) {
			return null;
		}
		// 返回队列头部元素并移除：先入先出
		return userWaitQueue.poll();
	}
	/**
	 * 返回指定用户所在队列
	 * @param userId
	 * @return
	 */
	public Queue<ChatMsgDetailDto> getUserQueueFromQueues(String userId){
		// 找出客服队列指针
		String userQueueId = userQueues.get(userId);
		// 根据客服队列指针找出真实 客服队列
		return waitQueues.get(userQueueId);
	}
	
	/**
	 * 从chatId的等待队列中移除第一个元素：userId
	 * @param userId
	 */
	public void removeChatQueueUser(String chatId,String userId) {
		// 从队列中移除一个消息，则若全局队列是满的，要修改为未满
		if(isFull) {
			isFull = false;
		}
		logger.debug("从客服"+chatId+"的等待队列中移除头部元素"+userId);
		// 移除并返问队列头部的元素    如果队列为空，则返回null
		Queue<ChatMsgDetailDto> userWaitQueue = getChatQueue(chatId);
		logger.debug("客服"+chatId+"的等待队列为："+userWaitQueue);
		if(userWaitQueue.peek()!=null && userWaitQueue.peek().getFormeUser().equals(userId)) {
			// 返回队列头部元素：先入先出
			userWaitQueue.poll();
		}
		logger.debug("移除头部元素"+userId+"之后，客服"+chatId+"的等待队列为："+getChatQueue(chatId));
		logger.debug("移除用户消息之后，清理用户消息队列指针");
		userQueues.remove(userId);
		logger.debug("清理用户等待队列指针之后："+userQueues.get(userId));
	}
	
	/**
	 * 客服下线，移除客服队列，其中的等待列队需要更新
	 * @param chatId		需要移除的客服的ID
	 * @param resetAllQueue	是否需要移除客服队列后，重排消息队列
	 */
	public void removeChatQueue(String chatId,boolean resetAllQueue) {
		List<String> newUsefulChats = getUsefulChats();
		newUsefulChats.remove(chatId);
		if(resetAllQueue==true) {
			// 设置可用客服列表，重排队列，清理客服、用户的队列指针
			setUsefulChats(newUsefulChats);
			return;
		}
		// 单纯移除消息队列，不重排的话，还需要清理等待队列中的消息已经队列指针
		String charQueueId = chatQueues.get(chatId);
		Queue<ChatMsgDetailDto> chatQueue = waitQueues.get(charQueueId);
		if(CollectionUtils.isNotEmpty(chatQueue)) {
			// 清理用户消息指针
			for(ChatMsgDetailDto deleteMsgEntity : chatQueue) {
				userQueues.remove(deleteMsgEntity.getFormeUser());
			}
		}
		// 清理客服队列指针
		chatQueues.remove(chatId);
		// 移除消息队列数据
		waitQueues.remove(charQueueId);
	}
	
	/**
	 * 根据需要，重排客服队列
	 */
	private void resetChatQueue(List<String> removeChats,List<String> addChats) {
		logger.debug("开始重排所有客服队列");
		logger.debug("需要移除的客服列表："+removeChats);
		logger.debug("需要新增的客服列表："+addChats);
		// 若下线客服数量少于上线客服数量，则直接把消息等待队列移动即可，若下线客服数量大于上线客服数量，则除了做消息等待队列的转移，还需要把多余的等待队列中的客户重新加入到消息队列中
		// 先遍历新上线客服，将所有下线客服的等待队列迁移过来
		List<String> tempRemoveChats = new ArrayList<String>();
		tempRemoveChats.addAll(removeChats);
		for(String tempRemoveChat : removeChats) {
			// 队列指针
			String queueId = chatQueues.get(tempRemoveChat);
			if(addChats.size()<=0) {
				break;
			}
			String newChatId = addChats.get(0);
			logger.debug("移除客服队列开始："+tempRemoveChat+" - "+newChatId);
			// 移除旧的队列
			chatQueues.remove(tempRemoveChat);
			chatQueues.put(newChatId, queueId);
			// 移除新上线的客服，聊天队列迁移之后，按照正常客服对待
			addChats.remove(newChatId);
			tempRemoveChats.remove(tempRemoveChat);
			logger.debug("移除旧客服"+tempRemoveChat+"，转移队列到新客服"+newChatId);
		}
		// 若下线客服的消息等待队列还未处理完，则按照最新用户消息对待
		if(CollectionUtils.isNotEmpty(tempRemoveChats)) {
			logger.debug("多余的客服队列："+tempRemoveChats);
			logger.debug("客服队列转接后，未能安置的用户消息 ，按照新入消息重新进入队列");
			List<Queue<ChatMsgDetailDto>> unRemoveWaitQueues = new ArrayList<Queue<ChatMsgDetailDto>>();
			// 获取未能安置的用户消息
			for(String tempRemoveChat : tempRemoveChats) {
				String queueId = chatQueues.get(tempRemoveChat);
				Queue<ChatMsgDetailDto> queue = waitQueues.get(queueId);
				unRemoveWaitQueues.add(queue);
				removeChatQueue(tempRemoveChat,false);
			}
			logger.debug("临时存储队列集合："+unRemoveWaitQueues);
				for(Queue<ChatMsgDetailDto> tempQueue : unRemoveWaitQueues) {
					if(tempQueue!=null) {
						for(ChatMsgDetailDto tempMsg : tempQueue) {
							// 消息重排暂时设置消息内容为空 未完成
							tempMsg.setContent(null);
							addQueue(tempMsg);
						}
					}
				}
			logger.debug("最后移除客服指针（可用客服队列已经在setUseFulChats方法中移除）");
			for(String tempRemoveChatId : tempRemoveChats) {
				chatQueues.remove(tempRemoveChatId);
			}
			logger.debug("移除客服指针之后，客服指针："+chatQueues);
		}
		logger.debug("重排完毕");
	}
	
	/**
	 * 通用校验
	 * @return
	 */
	public boolean valiate() {
		if(isFull) {
			return false;
		}
		if(CollectionUtils.isEmpty(usefulChats)) {
			return false;
		}
		return true;
	}
	public List<String> getUsefulChats() {
		return usefulChats;
	}
	
	/**
	 * 重新设置可用客服列表，重排消息队列
	 * @param chats
	 */
	public void setUsefulChats(List<String> chats) {
		logger.debug("设置可用客服："+chats);
		isFull = false;// 重置全局队列标志位
		// 若客服队列设置为空 ，则所有客服均下线，清空队列
		if(CollectionUtils.isEmpty(chats)) {
			logger.debug("设置的可用客服为空，重置所有数据");
			waitQueues = new HashMap<String,Queue<ChatMsgDetailDto>>();
			userQueues = new HashMap<String,String>();
			chatQueues = new HashMap<String,String>();
		}
		if(usefulChats == null) {
			usefulChats = chats;
		}else {
			List<String> removeChats = new ArrayList<String>();
			List<String> addChats = new ArrayList<String>();
			for(String oldChatId : usefulChats) {
				// 若旧的客服列表中的客服，存在于新客服列表，则无需做出改变
				if(chats.contains(oldChatId)) {
					continue;
				}
				// 若旧的客服列表中的客服不存在于新客服列表，则此客服已下线，需要重排队列
				removeChats.add(oldChatId);
			}
			for(String newChatId : chats) {
				// 若新的客服列表中的客服，存在于旧客服列表，则无需做出改变
				if(usefulChats.contains(newChatId)) {
					continue;
				}
				// 若新的客服列表中的客服不存在于旧客服列表，则此客服为新增客服，需要修改等待队列
				addChats.add(newChatId);
			}
			// 统计客服增加后，修改全局值
			usefulChats = chats;
			// 重排队列
			resetChatQueue(removeChats,addChats);
		}
		logger.debug("客服设置完成："+usefulChats);
	}
	
	/**
	 * 打印整体队列
	 */
	public void printAllQueue() {
		logger.debug("开始打印所有队列");
		logger.debug("可用客服列表："+usefulChats);
		logger.debug("客服队列指针："+chatQueues);
		logger.debug("用户队列指针："+userQueues);
		for(String chatId : chatQueues.keySet()) {
			printChatQueue(chatId);
		}
		logger.debug("打印所有队列结束");
	}
	public void printChatQueue(String chatId) {
		
		logger.debug("开始打印客服"+chatId+"的等待队列");
		Queue<ChatMsgDetailDto> chatQueue = getChatQueue(chatId);
		logger.debug(chatId+"客服队列：");
		int i=0;
		for(ChatMsgDetailDto tempEntity : chatQueue) {
			i++;
			logger.debug("客服"+chatId+"的等待队列中，第"+i+"个等待信息为："+tempEntity);
		}
		logger.debug("打印客服"+chatId+"的队列结束");
	}
	
	public static void main(String[] args) {
		ChatWaitQueueService main = ChatWaitQueueService.newInstance();
		logger.debug("\ntest - 客服数据初始化:\n");
		logger.debug("设置客服数据开始:");
		Integer chatCount = 5;
		List<String> chats = new ArrayList<String>();
		for(Integer i=1;i<(chatCount+1);i++) {
			chats.add(i.toString());
		}
		logger.debug("设置客服数据"+chats);
		main.setUsefulChats(chats);
		logger.debug("设置客服数据完毕，打印所有队列");
		main.printAllQueue();
		
		logger.debug("\ntest - 向队列中添加一个消息:\n");
		ChatMsgDetailDto testOneMsg = new ChatMsgDetailDto();
		testOneMsg.setFormeUser("1-1");
		testOneMsg.setMsgType(WxMaterialTypeEnum.text);
		testOneMsg.setCreateTime(new Date());
		testOneMsg.setContent("第一个加入队列的人");
		logger.debug("消息内容："+testOneMsg);
		main.addQueue(testOneMsg);
		logger.debug("插入队列完毕，打印所有队列");
		main.printAllQueue();
		
		logger.debug("\ntest - 填满队列:\n");
		for(Integer i=0;i<chatCount*MAX_QUEUE_LENGTH;i++) {
			ChatMsgDetailDto testAllMsg = new ChatMsgDetailDto();
			testAllMsg.setFormeUser("2-"+i);
//			testAllMsg.setFormeUser(new Date().getTime()+"");
			testAllMsg.setMsgType(WxMaterialTypeEnum.text);
			testAllMsg.setCreateTime(new Date());
			testAllMsg.setContent("第"+i+"个加入队列的人");
			logger.debug("消息内容："+testAllMsg);
			boolean addFlag = main.addQueue(testAllMsg);
			if(!addFlag) {
				logger.debug("队列插入失败，队列已满");
				break;
			}
		}
		logger.debug("队列已填满，打印所有队列");
		main.printAllQueue();
		
		logger.debug("\ntest - 使用规定模式获取并移除客服1的消息等待队列中第一个元素:\n");
		ChatMsgDetailDto testThreeMsg = main.getChatQueueUser("1");
		logger.debug("取得消息队列中的消息："+testThreeMsg);
		logger.debug("移除前打印客服1的队列");
		main.printChatQueue("1");
		logger.debug("移除已经取出的消息");
		main.removeChatQueueUser("1", testThreeMsg.getFormeUser());
		logger.debug("移除后打印客服1的队列");
		main.printChatQueue("1");
		logger.debug("取出等待的第一个消息，之后，打印所有队列");
		main.printAllQueue();
		
		logger.debug("\ntest - 已经移除了队列中的一个消息，现在追加一个消息，看是否可以添加成功:\n");
		ChatMsgDetailDto testAllMsg = new ChatMsgDetailDto();
		testAllMsg.setFormeUser("1-1");
		testAllMsg.setMsgType(WxMaterialTypeEnum.text);
		testAllMsg.setCreateTime(new Date());
		testAllMsg.setContent("第一个加入队列的人，我又回来啦");
		logger.debug("消息内容："+testAllMsg);
		main.addQueue(testAllMsg);
		logger.debug("追加消息之后，打印所有队列");
		main.printAllQueue();
		
		logger.debug("\ntest - 不使用规定模式获取并移除客服1的消息等待队列中第一个元素:\n");
		ChatMsgDetailDto fourThreeMsg = main.getChatQueueUserAndDeleteFromQueue("1");
		logger.debug("取得并移除消息队列中的消息："+fourThreeMsg);
		logger.debug("移除后打印客服1的队列");
		main.printChatQueue("1");
		logger.debug("取出等待的第一个消息，之后，打印所有队列");
		main.printAllQueue();
		
		logger.debug("\ntest - 重新设置客服，上线客服数量=下线客服数量【3、4、5、6、7】:\n");
		List<String> newChats = new ArrayList<String>();
		for(Integer i=3;i<(chatCount+3);i++) {
			newChats.add(i.toString());
		}
		logger.debug("要设置的新客服："+newChats);
		main.setUsefulChats(newChats);
		logger.debug("设置完新客服，全局队列：");
		main.printAllQueue();
		
		logger.debug("\ntest - 重新设置客服，上线客服数量<下线客服数量【2、3、4、5】:\n");
		List<String> newChats3 = new ArrayList<String>();
		for(Integer i=2;i<(chatCount+1);i++) {
			newChats3.add(i.toString());
		}
		logger.debug("要设置的新客服："+newChats3);
		main.setUsefulChats(newChats3);
		logger.debug("设置完新客服，全局队列：");
		main.printAllQueue();
		
		logger.debug("\ntest - 重新设置客服，上线客服数量>下线客服数量【3、4、5、6、7】:\n");
		List<String> newChats2 = new ArrayList<String>();
		for(Integer i=3;i<(chatCount+3);i++) {
			newChats2.add(i.toString());
		}
		logger.debug("要设置的新客服："+newChats2);
		main.setUsefulChats(newChats2);
		logger.debug("设置完新客服，全局队列：");
		main.printAllQueue();
		
		// 未完成，由于同一个人 ，可能发送多条消息给客服，所以，对于每次排队中的用户，发送的多条消息 ，插入到一个队列中，追加消息内容。
		// 防止一个用户，在多个队列中存在，多次排队
		logger.debug("\ntest - 已经存在于等待队列的客户重复发送消息:\n");
		ChatMsgDetailDto addByUserDto = new ChatMsgDetailDto();
		addByUserDto.setFormeUser("1-1");
		addByUserDto.setMsgType(WxMaterialTypeEnum.text);
		addByUserDto.setContent("第一个加入队列的人，我想多发点消息");
		addByUserDto.setCreateTime(new Date());
		logger.debug("插入队列中已经存在的用户，"+addByUserDto);
		main.addQueue(addByUserDto);
		logger.debug("插入完毕，全局队列：");
		main.printAllQueue();
	}
	/**
	 * 判断指定客服的等待队列是否已经满
	 * @param chatId
	 */
	public boolean isFullQueue(String chatId) {
		Queue<ChatMsgDetailDto> chatQueue = getChatQueue(chatId);
		if(chatQueue.size()>=MAX_QUEUE_LENGTH) {
			return true;
		}else {
			return false;
		}
	}
}

